package vn.wallet.app.helper.exceptions;

import java.util.Iterator;

import javax.faces.FacesException;
import javax.faces.application.NavigationHandler;
import javax.faces.application.ViewExpiredException;
import javax.faces.context.ExceptionHandler;
import javax.faces.context.ExceptionHandlerWrapper;
import javax.faces.context.FacesContext;
import javax.faces.event.ExceptionQueuedEvent;
import javax.faces.event.ExceptionQueuedEventContext;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

public class MyExceptionHandler extends ExceptionHandlerWrapper {

	private final ExceptionHandler wrapped;
	private static final Logger LOG = LoggerFactory.getLogger(ExceptionHandler.class);

	protected MyExceptionHandler(ExceptionHandler wrapped) {
		this.wrapped = wrapped;
	}

	@Override
	public ExceptionHandler getWrapped() {
		return this.wrapped;
	}

	@Override
	public void handle() throws FacesException {
		Iterable<ExceptionQueuedEvent> events = this.wrapped.getUnhandledExceptionQueuedEvents();
		for (Iterator<ExceptionQueuedEvent> it = events.iterator(); it.hasNext();) {
			ExceptionQueuedEvent event = it.next();
			ExceptionQueuedEventContext eqec = event.getContext();
			Throwable t = eqec.getException();

			// TOTO specifiy clearly the BusinessException and
			// TechnicalException
			if (t instanceof ViewExpiredException || t instanceof BusinessException || t instanceof TechnicalException) {
				FacesContext context = eqec.getContext();
				NavigationHandler navHandler = context.getApplication().getNavigationHandler();
				try {
					LOG.info("{}: {}", t.getClass().getSimpleName(), t.getMessage());
					t.printStackTrace();
					navHandler.handleNavigation(context, null, "login?faces-redirect=true&expired=true");
				} finally {
					it.remove();
				}
			}
			// TODO catch event FileNotFoundException && HandledException ....
		}

		this.wrapped.handle();
		;
	}
}
